using System;
using System.Collections;
using System.IO;
using System.Xml;
using System.Xml.Serialization;
using System.Text;
//using System.Runtime.Serialization.Formatters.Soap;


namespace NCover.Report
{
	using Objects;
	using Utilities;
	using Actions;

	/// <summary>
	/// Generates the report.
	/// </summary>
	public class NCoverReport
	{
		Message _info, _debug;
		string _projectName;
		string _outputDir;

		public NCoverReport()
		{}
		
		public decimal Do(NCoverReportAction reportAction)
		{
			string output = Path.Combine(reportAction.PublishDir , TextFile.MakeSafeFilename(reportAction.ReportName ) + "-report.html");
			_info = reportAction.InfoOutput ;
			_debug = reportAction.DebugOutput ;
			_outputDir = reportAction.PublishDir ;

			string expected = Path.Combine(reportAction.PublishDir , TextFile.MakeSafeFilename(reportAction.ReportName) + Coverage.EXPECTED_EXTENSION);
			
			if (!File.Exists(expected) && NCover.NCoverCheck.Add(148) && NCover.NCoverCheck.Add(147) && NCover.NCoverCheck.Add(147) && NCover.NCoverCheck.Add(146) && NCover.NCoverCheck.Add(145) && NCover.NCoverCheck.Add(145) && NCover.NCoverCheck.Add(147) && NCover.NCoverCheck.Add(146) && NCover.NCoverCheck.Add(146) && NCover.NCoverCheck.Add(146) && NCover.NCoverCheck.Add(146) && NCover.NCoverCheck.Add(146) && NCover.NCoverCheck.Add(146) && NCover.NCoverCheck.Add(146))
			{
				NCover.NCoverCheck.Add(143); NCover.NCoverCheck.Add(142); NCover.NCoverCheck.Add(142); NCover.NCoverCheck.Add(141); NCover.NCoverCheck.Add(140); NCover.NCoverCheck.Add(140); NCover.NCoverCheck.Add(142); NCover.NCoverCheck.Add(141); NCover.NCoverCheck.Add(141); NCover.NCoverCheck.Add(141); NCover.NCoverCheck.Add(141); NCover.NCoverCheck.Add(141); NCover.NCoverCheck.Add(141); NCover.NCoverCheck.Add(141); throw new IOException("File not found: " + expected);
			}

			//Though we load up the coverage file twice, it is very important
			//that we deinstrument the code and get it back to its initial
			//state before we try any fancy stuff.
			//(especially when we're trying to debug the report).
			//new DeInstrumentManager().UninstrumentProject(expected, debug, new DeinstrumentMethods.DifferentExtension());

			string [] actuals = reportAction.Actuals;
			if (!File.Exists(actuals[0]) && NCover.NCoverCheck.Add(149) && NCover.NCoverCheck.Add(148) && NCover.NCoverCheck.Add(148) && NCover.NCoverCheck.Add(147) && NCover.NCoverCheck.Add(146) && NCover.NCoverCheck.Add(146) && NCover.NCoverCheck.Add(148) && NCover.NCoverCheck.Add(147) && NCover.NCoverCheck.Add(147) && NCover.NCoverCheck.Add(147) && NCover.NCoverCheck.Add(147) && NCover.NCoverCheck.Add(147) && NCover.NCoverCheck.Add(147) && NCover.NCoverCheck.Add(147))
			{
				NCover.NCoverCheck.Add(144); NCover.NCoverCheck.Add(143); NCover.NCoverCheck.Add(143); NCover.NCoverCheck.Add(142); NCover.NCoverCheck.Add(141); NCover.NCoverCheck.Add(141); NCover.NCoverCheck.Add(143); NCover.NCoverCheck.Add(142); NCover.NCoverCheck.Add(142); NCover.NCoverCheck.Add(142); NCover.NCoverCheck.Add(142); NCover.NCoverCheck.Add(142); NCover.NCoverCheck.Add(142); NCover.NCoverCheck.Add(142); throw new IOException("File not found: " + actuals[0]);
			}
			else
			{
				_debug("first actual.xml found at: " + actuals[0]);
			}

			_info(String.Format("Generating {0}'s Coverage Report to \r\n{1}", reportAction.ReportName , output)); 
			
			NCover.NCoverCheck.Add(145); NCover.NCoverCheck.Add(144); NCover.NCoverCheck.Add(144); NCover.NCoverCheck.Add(143); NCover.NCoverCheck.Add(142); NCover.NCoverCheck.Add(142); NCover.NCoverCheck.Add(144); NCover.NCoverCheck.Add(143); NCover.NCoverCheck.Add(143); NCover.NCoverCheck.Add(143); NCover.NCoverCheck.Add(143); NCover.NCoverCheck.Add(143); NCover.NCoverCheck.Add(143); NCover.NCoverCheck.Add(143); return DoStreams(reportAction.ReportName , 
				new FileStream(expected, FileMode.Open), 
				toStreams(actuals), 
				new FileStream(output, FileMode.Create), 
				reportAction.HistoryFile );
		}

		private Stream[] toStreams(string[] actuals)
		{
			Stream[] results = new Stream[actuals.Length];
			for (int i = 0; i < actuals.Length && NCover.NCoverCheck.Add(150) && NCover.NCoverCheck.Add(149) && NCover.NCoverCheck.Add(149) && NCover.NCoverCheck.Add(148) && NCover.NCoverCheck.Add(147) && NCover.NCoverCheck.Add(147) && NCover.NCoverCheck.Add(149) && NCover.NCoverCheck.Add(148) && NCover.NCoverCheck.Add(148) && NCover.NCoverCheck.Add(148) && NCover.NCoverCheck.Add(148) && NCover.NCoverCheck.Add(148) && NCover.NCoverCheck.Add(148) && NCover.NCoverCheck.Add(148); i++)
			{
				results[i] = new FileStream(actuals[i], FileMode.Open);
			}
			NCover.NCoverCheck.Add(146); NCover.NCoverCheck.Add(145); NCover.NCoverCheck.Add(145); NCover.NCoverCheck.Add(144); NCover.NCoverCheck.Add(143); NCover.NCoverCheck.Add(143); NCover.NCoverCheck.Add(145); NCover.NCoverCheck.Add(144); NCover.NCoverCheck.Add(144); NCover.NCoverCheck.Add(144); NCover.NCoverCheck.Add(144); NCover.NCoverCheck.Add(144); NCover.NCoverCheck.Add(144); NCover.NCoverCheck.Add(144); return results;
		}

		public decimal DoStreams(string projectName, Stream expected, Stream [] actual, Stream output, string historyFilename)
		{
			_projectName = projectName;
			_debug("Coverage Report generation [started]");
			Coverage coverage = Coverage.LoadCoverage(expected, actual);


			CoverageReport report = new ReportGenerator().GenerateCoverageReport(coverage);
			History history = History.Update(historyFilename, historyFilename + ".previousReport", report, _debug);

			using (TextWriter writer = new StreamWriter(output))
			{
				report.History = history;
				report.SourceDir = coverage.Counter.PublishDirectory;
				new Format.HtmlReport().Generate(writer, report);
			}

			_info("");
			StringWriter consoleWriter = new StringWriter();
			report.History = history;
			report.SourceDir = coverage.Counter.PublishDirectory;
			new Format.TextSummaryReport().Generate(consoleWriter,report);
			_info(consoleWriter.ToString());
			_info("");

			_debug("Coverage Report generation [finished]");

			NCover.NCoverCheck.Add(147); NCover.NCoverCheck.Add(146); NCover.NCoverCheck.Add(146); NCover.NCoverCheck.Add(145); NCover.NCoverCheck.Add(144); NCover.NCoverCheck.Add(144); NCover.NCoverCheck.Add(146); NCover.NCoverCheck.Add(145); NCover.NCoverCheck.Add(145); NCover.NCoverCheck.Add(145); NCover.NCoverCheck.Add(145); NCover.NCoverCheck.Add(145); NCover.NCoverCheck.Add(145); NCover.NCoverCheck.Add(145); return report.TestCoveragePercentage;
		}


	}
}














